/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package org.ipo.mm.ejb.util;

/**
 *
 * @author makcro
 */
public class RepresentativeSearchQueryBuilder {

    private String nameFilter;
    private String nameOperator;
    private String telephoneFilter;
    private String telephoneOperator;
    private String faxFilter;
    private String faxOperator;
    private String emailFilter;
    private String emailOperator;
    private String functionFilter;
    private String functionOperator;
    private String[] institutionFilter;
    private String[] iTypeFilter;
    private String[] iRegionFilter;
    private String[] iFamilyFilter;
    private String[] iCityFilter;
    private String orderBy;
    private String query = new String();
    private boolean whereClauseAdded = false;
    private boolean isCount;
    private boolean isQuickSearch;
    String nextConditionClause = null;
    private boolean searchClauseOpened = false;

    public RepresentativeSearchQueryBuilder(
            String nameFilter,
            String nameOperator,
            String telephoneFilter,
            String telephoneOperator,
            String faxFilter,
            String faxOperator,
            String emailFilter,
            String emailOperator,
            String functionFilter,
            String functionOperator,
            String[] institutionFilter,
            String[] iTypeFilter,
            String[] iRegionFilter,
            String[] iFamilyFilter,
            String[] iCityFilter,
            boolean isCount,
            String orderBy,
            boolean isQuickSearch) {
        this.nameFilter = nameFilter;
        this.nameOperator = nameOperator;
        this.telephoneFilter = telephoneFilter;
        this.telephoneOperator = telephoneOperator;
        this.faxFilter = faxFilter;
        this.faxOperator = faxOperator;
        this.emailFilter = emailFilter;
        this.emailOperator = emailOperator;
        this.functionFilter = functionFilter;
        this.functionOperator = functionOperator;
        this.institutionFilter = institutionFilter;
        this.iTypeFilter = iTypeFilter;
        this.iRegionFilter = iRegionFilter;
        this.iFamilyFilter = iFamilyFilter;
        this.iCityFilter = iCityFilter;
        this.orderBy = orderBy;
        this.isQuickSearch = isQuickSearch;
        if (isCount) {
            query = " SELECT COUNT(r) FROM Representative r WHERE r.deleted = false ";

        } else {

            query = " SELECT r FROM Representative r WHERE r.deleted = false ";
        }

        if (this.isQuickSearch) {
            this.nextConditionClause = " \nOR\n ";

        } else {
            this.nextConditionClause = " \nAND\n ";
        }

    }

    public String getQuery() {

        if (this.nameFilter != null) {

            addNextConditionClause();


            query += " ( ";
            String expression = buildNameCondition(nameFilter, nameOperator);
            query += expression;
            query += " ) ";

        }

        if (this.emailFilter != null) {

            addNextConditionClause();


            query += " ( ";
            String expression = buildSimpleCondition(emailFilter, emailOperator, "r", "email");
            query += expression;
            query += " ) ";

        }

        if (this.faxFilter != null) {

            addNextConditionClause();


            query += " ( ";
            String expression = buildSimpleCondition(faxFilter, faxOperator, "r", "fax");
            query += expression;
            query += " ) ";

        }



        if (this.telephoneFilter != null) {
            addNextConditionClause();


            query += " ( ";
            String expression = buildSimpleCondition(telephoneFilter, telephoneOperator, "r", "telephone");
            query += expression;
            query += " ) ";

        }

        if (this.functionFilter != null) {
            addNextConditionClause();


            query += " ( ";
            String expression = buildSimpleCondition(functionFilter, functionOperator, "r", "function");
            query += expression;
            query += " ) ";

        }

        if (this.iCityFilter != null) {
            addNextConditionClause();


            query += " ( ";
            String expression = " r.institution.city.id " + buildSetCondition(iCityFilter);
            query += expression;
            query += " ) ";
        }

        if (this.iFamilyFilter != null) {

            addNextConditionClause();


            query += " ( ";
            String expression = " r.institution.family.id " + buildSetCondition(iFamilyFilter);
            query += expression;
            query += " ) ";
        }

        if (this.iRegionFilter != null) {
            addNextConditionClause();


            query += " ( ";
            String expression = " r.institution.region.id " + buildSetCondition(iRegionFilter);
            query += expression;
            query += " ) ";
        }

        if (this.iTypeFilter != null) {
            addNextConditionClause();


            query += " ( ";
            String expression = " r.institution.type.id " + buildSetCondition(iTypeFilter);
            query += expression;
            query += " ) ";
        }

        if (this.institutionFilter != null) {
            addNextConditionClause();


            query += " ( ";
            String expression = " r.institution.id " + buildSetCondition(institutionFilter);
            query += expression;
            query += " ) ";
        }

        closeSearchClause();
        
        if (orderBy != null && !this.isCount) {
            String orderByClause = " ORDER BY r." + orderBy;
            query += orderByClause;
        }

        
        
        return query;
    }

    private void openSearchCluase() {
        String clause = " AND ( \n";
        query += clause;
        this.searchClauseOpened = true;

    }

    private void closeSearchClause() {
        if (this.searchClauseOpened) {
            String closeExp = " )\n";
            query += closeExp;
        }
    }

    private void addNextConditionClause() {
        if (!this.searchClauseOpened) {
            openSearchCluase();
        } else {
            query += nextConditionClause;
        }
    }

    private String buildSimpleCondition(String filter,
            String filterOper,
            String entity,
            String attribute) {

        String expresion = "";
        String[] filters = filter.split(" ");



        for (int i = 0; i < filters.length; i++) {
            String someFilter = filters[i];
            expresion += " " + entity + "." + attribute + " LIKE '%" + someFilter + "%' ";
            if (i != filters.length - 1) {
                expresion += " " + filterOper + " ";
            }

        }
        return expresion;

    }

    private String buildSetCondition(String[] filter) {
        String expresion = " IN (";
        for (int i = 0; i < filter.length; i++) {
            String value = filter[i];
            expresion += value;
            if (i != filter.length - 1) {
                expresion += ", ";
            }

        }
        expresion += ")";

        return expresion;
    }

    private String buildNameCondition(String filter,
            String filterOper) {

        String expresion = "";
        String[] filters = filter.split(" ");
        for (int i = 0; i < filters.length; i++) {
            String someFilter = filters[i];

            expresion += " ( r.firstName LIKE '%" + someFilter + "%' OR r.lastName LIKE '%" + someFilter + "%')";

            if (i != filters.length - 1) {
                expresion += " " + filterOper + " ";
            }
        }

        return expresion;


    }
}
